package com.zcsy.manage.service.mall.impl;

import java.math.BigDecimal;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.zcsy.commons.constants.Constants;
import com.zcsy.commons.constants.OwnerConstants;
import com.zcsy.commons.unique.UniqueNumberUtils;
import com.zcsy.commons.util.DateUtils;
import com.zcsy.manage.model.base.CommonImg;
import com.zcsy.manage.model.base.ShopInfo;
import com.zcsy.manage.model.mall.GoodsCategory;
import com.zcsy.manage.model.mall.GoodsComment;
import com.zcsy.manage.model.mall.GoodsInfo;
import com.zcsy.manage.model.mall.GoodsSpecAttrNameValue;
import com.zcsy.manage.model.mall.GoodsSpecInfo;
import com.zcsy.manage.model.mall.GoodsSpecification;
import com.zcsy.manage.model.mall.GoodsSpecificationAttr;
import com.zcsy.manage.model.mall.OrderDetailInfo;
import com.zcsy.manage.model.mall.ShoppingCart;
import com.zcsy.manage.model.mall.vo.GoodsAttrInfo;
import com.zcsy.manage.persistence.base.ShopInfoDao;
import com.zcsy.manage.persistence.mall.GoodsInfoDao;
import com.zcsy.manage.persistence.mall.GoodsSpecificationAttrDao;
import com.zcsy.manage.persistence.mall.GoodsSpecificationDao;
import com.zcsy.manage.persistence.weixin.StringUtil;
import com.zcsy.manage.service.mall.IGoodsInfoService;

@Service
public class GoodsInfoServiceImpl implements IGoodsInfoService {

	@Autowired
	private GoodsInfoDao goodsInfoDao;
	
	@Autowired
	private ShopInfoDao shopInfoDao;
	
	@Autowired
	private GoodsSpecificationDao goodsSpecificationDao;
	
	@Autowired
	private GoodsSpecificationAttrDao goodsSpecificationAttrDao;
	
	@Override
	public List<GoodsInfo> getGoodsInfoByKeyword(GoodsInfo record) {
		return goodsInfoDao.getGoodsInfoByKeyword(record);
	}

	@Override
	public int insert(GoodsInfo record, List<GoodsAttrInfo> attrList) {
		String goodsId = record.getId();
		int specStock = 0;
		boolean hasSpec = false;
		
		/**
		 * 1、生成商品规格记录
		 * 2、生成规格属性记录
		 */
		GoodsSpecification spec = null;
		GoodsSpecificationAttr specAttr = null;
	    for(GoodsAttrInfo info : attrList) {
	        // 无规格信息
	        if(StringUtil.isEmptyString(info.getStock())){
                break;
            }
            spec = new GoodsSpecification();
            spec.setId(UniqueNumberUtils.get18UniqueNumber());
            spec.setGoodsId(goodsId);
            if(Constants.GOODS_TYPE_CARDS == record.getType()) {
                spec.setPrice(new BigDecimal(info.getPrice()));
                spec.setIntegralNum(spec.getPrice().intValue());
            } else {
                spec.setPrice(new BigDecimal(info.getPrice()));
            }
            spec.setStock(Integer.parseInt(info.getStock()));
            spec.setUserAccount(record.getUserAccount());
            spec.setSendTime(DateUtils.getFmtDate());
            
            hasSpec = true;
            specStock += Integer.parseInt(info.getStock());
            
            goodsSpecificationDao.insert(spec);
            
            if(!StringUtil.isEmptyString(info.getAttr1())){
                specAttr = new GoodsSpecificationAttr();
                specAttr.setId(UniqueNumberUtils.get18UniqueNumber());
                specAttr.setGoodsId(record.getId());
                specAttr.setSpecId(spec.getId());
                specAttr.setAttrName(info.getAttr1());
                specAttr.setAttrValue(info.getAttr1Value());
                specAttr.setUserAccount(record.getUserAccount());
                specAttr.setSendTime(DateUtils.getFmtDate());
                
                goodsSpecificationAttrDao.insert(specAttr);
            }
            if(!StringUtil.isEmptyString(info.getAttr2())){
                specAttr = new GoodsSpecificationAttr();
                specAttr.setId(UniqueNumberUtils.get18UniqueNumber());
                specAttr.setGoodsId(record.getId());
                specAttr.setSpecId(spec.getId());
                specAttr.setAttrName(info.getAttr2());
                specAttr.setAttrValue(info.getAttr2Value());
                specAttr.setUserAccount(record.getUserAccount());
                specAttr.setSendTime(DateUtils.getFmtDate());
                
                goodsSpecificationAttrDao.insert(specAttr);
            }
            if(!StringUtil.isEmptyString(info.getAttr3())){
                specAttr = new GoodsSpecificationAttr();
                specAttr.setId(UniqueNumberUtils.get18UniqueNumber());
                specAttr.setGoodsId(record.getId());
                specAttr.setSpecId(spec.getId());
                specAttr.setAttrName(info.getAttr3());
                specAttr.setAttrValue(info.getAttr3Value());
                specAttr.setUserAccount(record.getUserAccount());
                specAttr.setSendTime(DateUtils.getFmtDate());
                
                goodsSpecificationAttrDao.insert(specAttr);
            }
        }
	    if(hasSpec) {
	        record.setStock(specStock);
	    }
		return goodsInfoDao.insert(record);
	}

	@Override
	public int updateByPrimaryKey(GoodsInfo record) {
		return goodsInfoDao.updateByPrimaryKey(record);
	}

	@Override
	public GoodsInfo getGoodsInfoByPrimaryKey(String id) {
		return goodsInfoDao.getGoodsInfoByPrimaryKey(id);
	}

	@Override
	public int updateGoodsStateByMap(String id, int state) {
		Map map = new HashMap<String, Object>();
		map.put("id", id);
		map.put("state", state);
		return goodsInfoDao.updateGoodsStateByMap(map);
	}

	@Override
	public int deleteByUpdateState(String id) {
		return goodsInfoDao.deleteByUpdateState(id);
	}
	
	@Override
	public int updateSort(String id , String updateTime) {
		return goodsInfoDao.updateSort(id , updateTime);
	}
	
	@Override
	public List<GoodsInfo> getGoodsInfoByState() {
		return goodsInfoDao.getGoodsInfoByState();
	}

	@Override
	public List<GoodsInfo> getGoodsInfoBySales(String shopId) {
		return goodsInfoDao.getGoodsInfoBySales(shopId);
	}

	@Override
	public List<GoodsInfo> getIntegralGoodsInfo(Map<String, String> map) {
	    return goodsInfoDao.getIntegralGoodsInfo(map);
	}

	@Override
	public List<GoodsInfo> getSecKillGoodsList() {
		return goodsInfoDao.getSecKillGoodsList();
	}
	
	@Override
	public List<GoodsInfo> getWaitMsGoodsList() {
		return goodsInfoDao.getWaitMsGoodsList();
	}
	
	@Override
	public GoodsInfo getGoodsDetail(String goodsId) {
		return goodsInfoDao.getGoodsDetail(goodsId);
	}
	
	@Override
	public GoodsSpecInfo getGoodsInfoBySpecId(String specificationId) {
		return goodsInfoDao.getGoodsInfoBySpecId(specificationId);
	}
	
	@Override
	public List<GoodsInfo> getMsGoodsList() {
		return goodsInfoDao.getMsGoodsList();
	}
	
	@Override
	public  String[] getShopIdsByCellId(String cellId) {
		return goodsInfoDao.getShopIdsByCellId(cellId);
	}
	
	@Override
	public List<GoodsInfo> getSearchGoodsList(GoodsInfo goodsInfo, String[] shopIds) {
		Map map = new HashMap<String, Object>();
		map.put("shopIds", shopIds);
		map.put("goodsInfo", goodsInfo);
		return goodsInfoDao.getSearchGoodsList(map);
	}

	@Override
	public int updateGoodsInfo(List<OrderDetailInfo> detailList, Integer orderState) {
		int list = 0;
		for (OrderDetailInfo item : detailList) {
			GoodsInfo goods = goodsInfoDao.getGoodsInfoByPrimaryKey(item
					.getGoodsId());
			// 订单状态为待付款时，修改购买的商品，商品的规格的存储量
			if (orderState == OwnerConstants.NO_PAY_ORDER) {
				// 如果规格id不为空，则修改商品规格的数量，否则，修改商品的数量
				if (item.getSpecificationId() != null) {
					// 修改购买的商品的规格的存储量
					GoodsSpecification specification = goodsSpecificationDao
							.getGoodsSpecificationById(item
									.getSpecificationId());
					if (specification != null) {
						specification.setStock(specification.getStock() - item.getAmount());
						goodsSpecificationDao.updateGoodsSpecificationById(specification);
					}
				} else {
					// 修改购买的商品的存储量
					goods.setStock(goods.getStock() - item.getAmount());
				}
				goods.setSales(goods.getSales() + item.getAmount());
				// 如果商品的存储量为0，自动下架
				if (goods.getStock() == OwnerConstants.NO_GOODS_STOCK) {
					updateGoodsStateByMap(goods.getId(), Constants.GOODS_UNSALE);
				}
				//订单取消成功
			} else if (orderState == OwnerConstants.DROP_ORDER) {
				// 如果规格id不为空，则修改商品规格的数量，否则，修改商品的数量
				if (item.getSpecificationId() != null) {
					// 修改购买的商品的规格的存储量
					GoodsSpecification specification = goodsSpecificationDao.getGoodsSpecificationById(item.getSpecificationId());
					if (specification != null) {
						specification.setStock(specification.getStock() + item.getAmount());
						goodsSpecificationDao.updateGoodsSpecificationById(specification);
					}
				} else {
					// 修改购买的商品的存储量
					goods.setStock(goods.getStock() + item.getAmount());
				}
			}

			list = goodsInfoDao.updateByPrimaryKey(goods);

		}
		
		return list;
	}
	
	@Override
	public GoodsInfo getGoodsInfoDetail(String goodsId) {
		return goodsInfoDao.getGoodsInfoDetail(goodsId);
	}
	
	@Override
	public List<GoodsSpecAttrNameValue> getGoodsSpecAttrNameValueList(String goodsId) {
		return goodsInfoDao.getGoodsSpecAttrNameValueList(goodsId);
	}
	
	@Override
	public List<GoodsSpecification> getGoodsSpecWithValuesList(String goodsId) {
		return goodsInfoDao.getGoodsSpecWithValuesList(goodsId);
	}
	
	@Override
	public List<String> getAttrNameList(String goodsId) {
		return goodsInfoDao.getAttrNameList(goodsId);
	}
	@Override
	public List<String> getGoodsSpecInfoList(String goodsId) {
		return goodsInfoDao.getGoodsSpecInfoList(goodsId);
	}
	
	@Override
	public List<CommonImg> getGoodsImgList(String goodsId) {
		return goodsInfoDao.getGoodsImgList(goodsId);
	}
	
	@Override
	public List<GoodsInfo> getRelatedGoodsRecommend(String shopId,String goodsId) {
		Map map = new HashMap<String, Object>();
		map.put("shopId", shopId);
		map.put("goodsId", goodsId);
		return goodsInfoDao.getRelatedGoodsRecommend(map);
	}
	
	@Override
	public GoodsComment getGoodsDetailOneComment(String goodsId) {
		return goodsInfoDao.getGoodsDetailOneComment(goodsId);
	}
	
	@Override
	public int  getGoodsCommentNum(String goodsId) {
		return goodsInfoDao.getGoodsCommentNum(goodsId);
	}
	@Override
	public List<GoodsComment> getGoodsDetailAllComment(String goodsId) {
		return goodsInfoDao.getGoodsDetailAllComment(goodsId);
	}
	
	@Override
	public ShopInfo getShopInfo(String goodsId) {
		return goodsInfoDao.getShopInfo(goodsId);
	}
	
	@Override
	public List<ShopInfo> getShoppingCartInfoList(String userAccount,String cellId) {
		Map map = new HashMap<String, Object>();
		map.put("userAccount", userAccount);
		map.put("cellId", cellId);
		return goodsInfoDao.getShoppingCartInfoList(map);
	}
	
	@Override
	public List<GoodsCategory> getGoodsCategorysList() {
		return goodsInfoDao.getGoodsCategorysList();
	}
	
    @Override
    public List<GoodsInfo> selectGoodsInfoByKeyWords(GoodsInfo goodsInfo) {
        return goodsInfoDao.selectGoodsInfoByKeyWords(goodsInfo);
    }
        
        @Override
        public List<GoodsInfo> selectShopGoodsInfoByKeyWords(GoodsInfo goodsInfo) {
        	return goodsInfoDao.selectShopGoodsInfoByKeyWords(goodsInfo);
    }

	@Override
	public String getShopId(String shopId) {
		return goodsInfoDao.getShopId(shopId);
	}
	
	@Override
	public List<GoodsInfo> selectTopRecommendByParentId(String parentId) {
		return goodsInfoDao.selectTopRecommendByParentId(parentId);
	}
	
	@Override
	public List<GoodsInfo> getShopGoodsList(GoodsInfo goodsInfo) {
	    return goodsInfoDao.getShopGoodsList( goodsInfo);
	}

	@Override
	public List<GoodsInfo> getGoodsInfoByFilter(int order,int secType) {
		Map<String, Object> map = new HashMap<String, Object>();
		map.put("order", order);
		map.put("secType", secType);
		return goodsInfoDao.getGoodsInfoByFilter(map);
	}

	@Override
	public List<GoodsInfo> getIntegralGoodsByFilter(int order,int findIntegral,int min,int max) {
		Map<String, Object> map = new HashMap<String, Object>();
		map.put("order", order);
		map.put("findIntegral", findIntegral);
		map.put("min", min);
		map.put("max", max);
		return goodsInfoDao.getIntegralGoodsByFilter(map);
	}

	@Override
	public List<GoodsInfo> getByshopIdAndCategoryIdAndKeyword(String shopId,
			String categoryId, String keyword) {
		Map<String, Object> map = new HashMap<String, Object>();
		map.put("shopId", shopId);
		map.put("categoryId", categoryId);
		map.put("keyword", keyword);
		return goodsInfoDao.getByshopIdAndCategoryIdAndKeyword(map);
	}

	@Override
	public List<GoodsInfo> getGoodsInfoByName(String name, String cellId) {
		Map<String, Object> map = new HashMap<String, Object>();
		map.put("name", name);
		map.put("cellId", cellId);
		
		return goodsInfoDao.getGoodsInfoByName(map);
	}

	@Override
	public List<GoodsInfo> getmallGoodsByFilter(int order, String cellId) {
		Map<String, Object> map = new HashMap<String, Object>();
		map.put("order", order);
		map.put("cellId", cellId);

		return goodsInfoDao.getmallGoodsByFilter(map);
	}

	@Override
	public List<GoodsInfo> searchGoodsByCategoryId(String goodCategoryId,int order, String cellId) {
		Map<String, Object> map = new HashMap<String, Object>();
		map.put("goodsCategoryId", goodCategoryId);
		map.put("order", order);
		map.put("cellId", cellId);
		return goodsInfoDao.searchGoodsByCategoryId(map);
	}

    @Override
    public void updateGoodsInfoAndSpec(GoodsInfo record, List<GoodsAttrInfo> attrList) {
        String goodsId = record.getId();
        
        /**
         * 更新商品信息
         *     1、删除商品原对应的规格信息
         *     2、增加现对应的规格信息
         *     
         * 注：因订单和订单详情中已存在商品规格信息，故可先删除再添加，删除后购物车信息作为判断处理
         */
        
        goodsSpecificationAttrDao.deleteByGoodsId(goodsId);
        goodsSpecificationDao.deleteSpecificationByGoodsId(goodsId);
        
        GoodsSpecification spec = null;
        GoodsSpecificationAttr specAttr = null;
        for(GoodsAttrInfo info : attrList) {
            // 无规格信息
            if(StringUtil.isEmptyString(info.getStock())){
                break;
            }
            spec = new GoodsSpecification();
            spec.setId(UniqueNumberUtils.get18UniqueNumber());
            spec.setGoodsId(goodsId);
            if(Constants.GOODS_TYPE_CARDS == record.getType()) {
                spec.setPrice(new BigDecimal(info.getPrice()));
                spec.setIntegralNum(spec.getPrice().intValue());
            } else {
                spec.setPrice(new BigDecimal(info.getPrice()));
            }
            
            spec.setStock(Integer.parseInt(info.getStock()));
            spec.setUserAccount(record.getUserAccount());
            spec.setSendTime(DateUtils.getFmtDate());
            
            goodsSpecificationDao.insert(spec);
            
            if(!StringUtil.isEmptyString(info.getAttr1())){
                specAttr = new GoodsSpecificationAttr();
                specAttr.setId(UniqueNumberUtils.get18UniqueNumber());
                specAttr.setGoodsId(record.getId());
                specAttr.setSpecId(spec.getId());
                specAttr.setAttrName(info.getAttr1());
                specAttr.setAttrValue(info.getAttr1Value());
                specAttr.setUserAccount(record.getUserAccount());
                specAttr.setSendTime(DateUtils.getFmtDate());
                
                goodsSpecificationAttrDao.insert(specAttr);
            }
            if(!StringUtil.isEmptyString(info.getAttr2())){
                specAttr = new GoodsSpecificationAttr();
                specAttr.setId(UniqueNumberUtils.get18UniqueNumber());
                specAttr.setGoodsId(record.getId());
                specAttr.setSpecId(spec.getId());
                specAttr.setAttrName(info.getAttr2());
                specAttr.setAttrValue(info.getAttr2Value());
                specAttr.setUserAccount(record.getUserAccount());
                specAttr.setSendTime(DateUtils.getFmtDate());
                
                goodsSpecificationAttrDao.insert(specAttr);
            }
            if(!StringUtil.isEmptyString(info.getAttr3())){
                specAttr = new GoodsSpecificationAttr();
                specAttr.setId(UniqueNumberUtils.get18UniqueNumber());
                specAttr.setGoodsId(record.getId());
                specAttr.setSpecId(spec.getId());
                specAttr.setAttrName(info.getAttr3());
                specAttr.setAttrValue(info.getAttr3Value());
                specAttr.setUserAccount(record.getUserAccount());
                specAttr.setSendTime(DateUtils.getFmtDate());
                
                goodsSpecificationAttrDao.insert(specAttr);
            }
        }
        GoodsInfo oldInfo = goodsInfoDao.getGoodsInfoByPrimaryKey(record.getId());
        oldInfo.setType(record.getType());
        oldInfo.setName(record.getName());
        oldInfo.setStock(record.getStock());
        oldInfo.setGoodsCategoryId(record.getGoodsCategoryId());
        oldInfo.setSort(record.getSort());
        oldInfo.setPrice(record.getPrice());
        oldInfo.setMarketPrice(record.getMarketPrice());
        oldInfo.setUnit(record.getUnit());
        oldInfo.setKeyword(record.getKeyword());
        oldInfo.setIsRecommend(record.getIsRecommend());
        oldInfo.setDetail(record.getDetail());
        oldInfo.setUserAccount(record.getUserAccount());
        oldInfo.setLogo(record.getLogo());
        oldInfo.setUpdateTime(record.getUpdateTime());
        if(Constants.GOODS_TYPE_CARDS == record.getType()) {
            record.setPrice(new BigDecimal(record.getIntegralNum()));
        }
        goodsInfoDao.updateByPrimaryKey(record);
    }

	@Override
	public GoodsInfo getGoodsInfoByGoodsId(String goodsId) {
		return goodsInfoDao.getGoodsInfoByGoodsId(goodsId);
	}

	@Override
	public List<GoodsInfo> getGoodsAttrById(String id) {
		return goodsInfoDao.getGoodsAttrById(id);
	}

	@Override
	public List<GoodsInfo> getGoodsInfoBySpecIdAndGoodsId(String goodsId,String specId) {
		Map<String, Object> m = new HashMap<String, Object>();
		m.put("goodsId", goodsId);
		m.put("specId", specId);
		return goodsInfoDao.getGoodsInfoBySpecIdAndGoodsId(m);
	}

	@Override
	public List<GoodsInfo> getGoodsSales(String shopId) {
		return goodsInfoDao.getGoodsSales(shopId);
	}

	@Override
	public List<GoodsInfo> searchGoodsSalesByTime(String beginDate,String endDate,String shopId) {
		Map m = new HashMap();
		m.put("beginDate", beginDate);
		m.put("endDate", endDate);
		m.put("shopId", shopId);
		return goodsInfoDao.searchGoodsSalesByTime(m);
	}

	@Override
	public List<GoodsInfo> searchSaleByMonth(Integer secType,String beginDate, String endDate,String shopId) {
		Map m = new HashMap();
		m.put("secType", secType);
		m.put("beginDate", beginDate);
		m.put("endDate", endDate);
		m.put("shopId", shopId);
		return goodsInfoDao.searchSaleByMonth(m);
	}

	@Override
	public List<GoodsInfo> searchSalesVolumeByMonth(Integer secType,String beginDate, String endDate,String shopId) {
		Map m = new HashMap();
		m.put("secType", secType);
		m.put("beginDate", beginDate);
		m.put("endDate", endDate);
		m.put("shopId", shopId);
		
		return goodsInfoDao.searchSalesVolumeByMonth(m);
	}

	@Override
	public List<GoodsInfo> getGoodsByKeyword(GoodsInfo record) {
		return goodsInfoDao.getGoodsByKeyword(record);
	}

	@Override
	public List<GoodsInfo> selectGoodsInfoByAdCategoryId(Map<String, Object> params) {
		return goodsInfoDao.selectGoodsInfoByAdCategoryId(params);
	}

	@Override
	public List<GoodsInfo> getGoodsInfoByShopId(String shopId) {
		return goodsInfoDao.getGoodsInfoByShopId(shopId);
	}

    @Override
    public synchronized void updateGoodsStockAndSalesOrder(List<ShoppingCart> cartList) {
        // 更新商品库存
        for(ShoppingCart order : cartList) {
            if(!StringUtil.isEmptyString(order.getSpecificationId())) {
                GoodsSpecification goodsSpec = goodsSpecificationDao.getGoodsSpecById(order.getSpecificationId());
                goodsSpec.setStock(goodsSpec.getStock() - order.getAmount());
                goodsSpecificationDao.update(goodsSpec);
            } 
            GoodsInfo goodsInfo = goodsInfoDao.getGoodsInfoByPrimaryKey(order.getGoodsId());
            goodsInfo.setStock(goodsInfo.getStock() - order.getAmount());
            goodsInfo.setSales(goodsInfo.getSales() + order.getAmount());
            goodsInfoDao.updateByPrimaryKey(goodsInfo);
        }
    }
    
    
    
    @Override
    public synchronized void updateGoodsStockAndSalesCancel(List<OrderDetailInfo> detailList) {
        // 更新商品库存
        for(OrderDetailInfo info : detailList) {
            if(!StringUtil.isEmptyString(info.getSpecificationId())) {
                GoodsSpecification goodsSpec = goodsSpecificationDao.getGoodsSpecById(info.getSpecificationId());
                
                goodsSpec.setStock(goodsSpec.getStock() + info.getAmount());
                goodsSpecificationDao.update(goodsSpec);
            }
            
            GoodsInfo goodsInfo = goodsInfoDao.getGoodsInfoByPrimaryKey(info.getGoodsId());
            goodsInfo.setStock(goodsInfo.getStock() + info.getAmount());
            goodsInfo.setSales(goodsInfo.getSales() - info.getAmount());
            goodsInfoDao.updateByPrimaryKey(goodsInfo);
        }
    }

}